﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Content;

namespace Project3
{
    public class Ship : Collidable
    {
        PhibesGame game;
        Model model;

        Vector3 position = new Vector3(10000, 0, 0);
        float azimuth = (float)(3 * Math.PI / 2);      // Compass heading (radians, 0 is Z direction)
        float azimuthstep = 0.025f;

        float thrustUp = 0;
        float thrustForward = 4;

        bool destroyed = false;

        const float MinY = -100;
        const float MaxY = 100;

        const float Drag = 1;
        const float MaxThrust = 200;

        private Bullet bullets;

        public Bullet Bullets { get { return bullets; } }

        public float Azimuth { get { return azimuth; } set { azimuth = value; } }
        public float AzimuthStep { get { return azimuthstep; } set { azimuthstep = value; } }

        public float ThrustUp { get { return thrustUp; } set { thrustUp = value; } }
        public float ThrustForward { get { return thrustForward; } set { thrustForward = value; } }

        public bool Destroyed { get { return destroyed; } set { destroyed = value; } }

        public Matrix Transform { get { return Matrix.CreateTranslation(position); } }
        public override Vector3 Position { get { return position; } set { position = value; } }

        public override Vector3 Orientation { get { return Functions.FromAzimuth(azimuth); } }
        public override Vector3 Right { get { return Functions.FromAzimuth(azimuth + (float)(3 * Math.PI / 2)); } }

        public Ship(PhibesGame game)
        {
            this.game = game;
            bullets = new Bullet(game);

            AddCollisionPoint(0, 0, 1);
            AddCollisionPoint(0, 50, 1);
            AddCollisionPoint(0, -50, 1);
        }

        public void LoadContent(ContentManager content)
        {
            model = content.Load<Model>("Bat-rigid");
            bullets.LoadContent(content);
        }

        public void Update(GameTime gameTime)
        {
            Vector3 directedThrust = Orientation * thrustForward + new Vector3(0, thrustUp, 0);

            position += directedThrust * MaxThrust * (float)gameTime.ElapsedGameTime.TotalSeconds;
            position.Y = Math.Max(MinY, Math.Min(MaxY, position.Y));

            bullets.Update(gameTime);
        }

        public void Draw(GraphicsDeviceManager graphics, GameTime gameTime)
        {
            Matrix transform = Matrix.CreateScale(4) * Matrix.CreateRotationY(azimuth) * Matrix.CreateTranslation(position);

            if(!Destroyed)
                DrawModel(graphics, model, transform);
            bullets.Draw(graphics, gameTime);
        }

        private void DrawModel(GraphicsDeviceManager graphics, Model model, Matrix world)
        {
            Matrix[] transforms = new Matrix[model.Bones.Count];
            model.CopyAbsoluteBoneTransformsTo(transforms);

            foreach (ModelMesh mesh in model.Meshes)
            {
                foreach (BasicEffect effect in mesh.Effects)
                {
                    effect.EnableDefaultLighting();
                    effect.World = transforms[mesh.ParentBone.Index] * world;
                    effect.View = game.Camera.View;
                    effect.Projection = game.Camera.Projection;
                }
                mesh.Draw();
            }
        }

        public void Fire()
        {
            bullets.Fire(position, azimuth);
        }
    }
}